package top.wilsonlv.jaguar.cloud.auth.security;

import feign.FeignException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.web.authentication.AuthenticationFailureHandler;
import org.springframework.stereotype.Component;
import top.wilsonlv.jaguar.cloud.handlerlog.client.component.HandlerLogInterceptor;
import top.wilsonlv.jaguar.commons.web.exception.BaseException;
import top.wilsonlv.jaguar.commons.web.response.JsonResult;
import top.wilsonlv.jaguar.commons.web.response.ResultCode;
import top.wilsonlv.jaguar.openfeign.component.FeignExceptionHandler;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;

/**
 * @author lvws
 * @since 2021/6/8
 */
@Slf4j
@Component
public class LoginFailureHandler implements AuthenticationFailureHandler {

    @Autowired(required = false)
    private HandlerLogInterceptor handlerLogInterceptor;

    @Resource
    private FeignExceptionHandler feignExceptionHandler;

    @Override
    public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response,
                                        AuthenticationException exception) throws IOException {
        log.debug("用户登录失败：{}", exception.getMessage());

        JsonResult<?> result;
        if (exception.getCause() instanceof BaseException) {
            BaseException cause = (BaseException) exception.getCause();
            result = new JsonResult<>(cause.getResultCode(), null, cause.getMessage());
        } else if (exception.getCause() instanceof FeignException) {
            FeignException cause = (FeignException) exception.getCause();
            result = feignExceptionHandler.feignExceptionHandler(cause);
        } else {
            result = new JsonResult<>(ResultCode.CONFLICT, null, exception.getMessage());
        }

        response.setContentType(MediaType.APPLICATION_JSON_VALUE);
        try (PrintWriter writer = response.getWriter()) {
            writer.write(result.toJsonStr());
        }

        if (handlerLogInterceptor != null) {
            handlerLogInterceptor.log(request, response, null, null);
        }
    }
}
